<template>
  <div class="responsive-form" :class="formClasses">
    <el-form
      ref="formRef"
      :model="modelValue"
      :rules="rules"
      :label-position="labelPosition"
      :label-width="labelWidth"
      :size="formSize"
      :disabled="disabled"
      :inline="isInline && !isMobileDevice"
      v-bind="$attrs"
      @submit.prevent="handleSubmit"
    >
      <slot>
        <!-- 表单项会通过作用域插槽传入 -->
      </slot>
    </el-form>

    <!-- 表单操作按钮 -->
    <div class="form-actions" :class="actionsClasses" v-if="showActions">
      <slot name="actions">
        <el-button
          v-if="showCancel"
          @click="handleCancel"
          :disabled="loading"
        >
          {{ cancelText }}
        </el-button>
        <el-button
          type="primary"
          native-type="submit"
          :loading="loading"
          :disabled="disabled"
        >
          {{ submitText }}
        </el-button>
      </slot>
    </div>

    <!-- 移动端抽屉式表单 -->
    <el-drawer
      v-if="useMobileDrawer && isMobileDevice"
      v-model="drawerVisible"
      :title="title"
      direction="btt"
      size="90%"
      :with-header="!!title"
      @close="handleDrawerClose"
    >
      <div class="drawer-form-content">
        <el-form
          ref="drawerFormRef"
          :model="modelValue"
          :rules="rules"
          label-position="top"
          size="large"
          :disabled="disabled"
          @submit.prevent="handleSubmit"
        >
          <slot name="drawer-content">
            <slot></slot>
          </slot>
        </el-form>

        <div class="drawer-actions">
          <slot name="drawer-actions">
            <el-button
              v-if="showCancel"
              @click="handleDrawerCancel"
              :disabled="loading"
              block
            >
              {{ cancelText }}
            </el-button>
            <el-button
              type="primary"
              @click="handleDrawerSubmit"
              :loading="loading"
              :disabled="disabled"
              block
            >
              {{ submitText }}
            </el-button>
          </slot>
        </div>
      </div>
    </el-drawer>
  </div>
</template>

<script setup lang="ts">
import { ref, computed, watch, nextTick } from 'vue'
import { useResponsive } from '@/composables/useResponsive'
import type { FormInstance, FormRules } from 'element-plus'

interface Props {
  modelValue: Record<string, any>
  rules?: FormRules
  disabled?: boolean
  loading?: boolean
  inline?: boolean
  labelPosition?: 'left' | 'right' | 'top'
  labelWidth?: string | number
  size?: 'large' | 'default' | 'small'
  showActions?: boolean
  showCancel?: boolean
  submitText?: string
  cancelText?: string
  title?: string
  useMobileDrawer?: boolean
  responsive?: boolean
}

const props = withDefaults(defineProps<Props>(), {
  disabled: false,
  loading: false,
  inline: false,
  labelPosition: 'right',
  labelWidth: '120px',
  size: 'default',
  showActions: true,
  showCancel: true,
  submitText: '提交',
  cancelText: '取消',
  useMobileDrawer: false,
  responsive: true
})

const emit = defineEmits<{
  'update:modelValue': [value: Record<string, any>]
  submit: [value: Record<string, any>]
  cancel: []
  validate: [valid: boolean]
  drawerOpen: []
  drawerClose: []
}>()

const { isMobileDevice, getValue } = useResponsive()

// 响应式状态
const formRef = ref<FormInstance>()
const drawerFormRef = ref<FormInstance>()
const drawerVisible = ref(false)

// 计算属性
const formClasses = computed(() => ({
  'responsive': props.responsive,
  'mobile': isMobileDevice.value,
  'inline': props.inline && !isMobileDevice.value,
  'loading': props.loading,
  'disabled': props.disabled
}))

const actionsClasses = computed(() => ({
  'mobile-actions': isMobileDevice.value,
  'stacked': isMobileDevice.value
}))

const labelPosition = computed(() => {
  if (isMobileDevice.value) {
    return 'top'
  }
  return props.labelPosition
})

const labelWidth = computed(() => {
  if (isMobileDevice.value) {
    return 'auto'
  }
  return getValue({
    xs: '80px',
    sm: '100px',
    md: '120px',
    lg: '140px',
    xl: '160px'
  }, props.labelWidth as string)
})

const formSize = computed(() => {
  if (isMobileDevice.value) {
    return 'large'
  }
  return props.size
})

const isInline = computed(() => {
  return props.inline && !isMobileDevice.value
})

// 方法
const validate = async (): Promise<boolean> => {
  try {
    if (props.useMobileDrawer && isMobileDevice.value && drawerVisible.value) {
      await drawerFormRef.value?.validate()
    } else {
      await formRef.value?.validate()
    }
    return true
  } catch (error) {
    return false
  }
}

const clearValidate = () => {
  formRef.value?.clearValidate()
  drawerFormRef.value?.clearValidate()
}

const resetFields = () => {
  formRef.value?.resetFields()
  drawerFormRef.value?.resetFields()
}

const scrollToField = (prop: string) => {
  nextTick(() => {
    if (props.useMobileDrawer && isMobileDevice.value && drawerVisible.value) {
      drawerFormRef.value?.scrollToField(prop)
    } else {
      formRef.value?.scrollToField(prop)
    }
  })
}

const handleSubmit = async () => {
  const valid = await validate()
  emit('validate', valid)

  if (valid) {
    emit('submit', props.modelValue)
  }
}

const handleCancel = () => {
  emit('cancel')
}

const handleDrawerSubmit = async () => {
  const valid = await validate()
  emit('validate', valid)

  if (valid) {
    emit('submit', props.modelValue)
    drawerVisible.value = false
  }
}

const handleDrawerCancel = () => {
  drawerVisible.value = false
  emit('cancel')
}

const handleDrawerClose = () => {
  emit('drawerClose')
}

// 打开抽屉
const openDrawer = () => {
  if (props.useMobileDrawer && isMobileDevice.value) {
    drawerVisible.value = true
    emit('drawerOpen')
  }
}

// 关闭抽屉
const closeDrawer = () => {
  drawerVisible.value = false
  emit('drawerClose')
}

// 监听移动端变化
watch(isMobileDevice, (mobile) => {
  if (props.useMobileDrawer && mobile) {
    // 切换到移动端时，如果需要可以自动打开抽屉
    // drawerVisible.value = true
  }
})

// 暴露方法
defineExpose({
  validate,
  clearValidate,
  resetFields,
  scrollToField,
  openDrawer,
  closeDrawer,
  formRef,
  drawerFormRef
})
</script>

<script lang="ts">
// 添加组件名称，便于调试和开发工具识别
export default {
  name: 'ResponsiveForm'
}
</script>

<style scoped>
.responsive-form {
  width: 100%;
}

.responsive-form.mobile {
  padding: 0;
}

.responsive-form.loading {
  position: relative;
}

.responsive-form.loading::after {
  content: '';
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background: rgba(255, 255, 255, 0.7);
  z-index: 1;
}

/* 响应式表单项布局 */
:deep(.el-form) {
  width: 100%;
}

:deep(.el-form-item) {
  margin-bottom: 20px;
}

:deep(.el-form-item__label) {
  font-weight: 500;
  line-height: 1.4;
}

:deep(.el-form-item__content) {
  line-height: 1.4;
}

/* 移动端表单项样式 */
.responsive-form.mobile :deep(.el-form-item) {
  margin-bottom: 24px;
}

.responsive-form.mobile :deep(.el-form-item__label) {
  font-size: 14px;
  margin-bottom: 8px;
  line-height: 1.4;
}

.responsive-form.mobile :deep(.el-form-item__content) {
  font-size: 16px;
}

/* 输入框响应式样式 */
:deep(.el-input__wrapper) {
  transition: all 0.3s ease;
}

.responsive-form.mobile :deep(.el-input__wrapper) {
  min-height: 44px;
  font-size: 16px;
}

:deep(.el-input__inner) {
  transition: all 0.3s ease;
}

.responsive-form.mobile :deep(.el-input__inner) {
  font-size: 16px;
  height: 44px;
}

/* 选择器响应式样式 */
:deep(.el-select .el-input__wrapper) {
  min-height: 32px;
}

.responsive-form.mobile :deep(.el-select .el-input__wrapper) {
  min-height: 44px;
}

/* 文本域响应式样式 */
:deep(.el-textarea__inner) {
  transition: all 0.3s ease;
}

.responsive-form.mobile :deep(.el-textarea__inner) {
  min-height: 100px;
  font-size: 16px;
  padding: 12px;
}

/* 单选框组响应式样式 */
:deep(.el-radio-group) {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
}

.responsive-form.mobile :deep(.el-radio-group) {
  flex-direction: column;
  gap: 16px;
}

.responsive-form.mobile :deep(.el-radio) {
  margin-right: 0;
  min-height: 44px;
  display: flex;
  align-items: center;
}

/* 多选框组响应式样式 */
:deep(.el-checkbox-group) {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
}

.responsive-form.mobile :deep(.el-checkbox-group) {
  flex-direction: column;
  gap: 16px;
}

.responsive-form.mobile :deep(.el-checkbox) {
  margin-right: 0;
  min-height: 44px;
  display: flex;
  align-items: center;
}

/* 开关响应式样式 */
.responsive-form.mobile :deep(.el-switch) {
  height: 28px;
}

.responsive-form.mobile :deep(.el-switch__core) {
  height: 28px;
  width: 52px;
}

.responsive-form.mobile :deep(.el-switch__action) {
  height: 24px;
  width: 24px;
}

/* 滑块响应式样式 */
:deep(.el-slider) {
  margin: 16px 0;
}

.responsive-form.mobile :deep(.el-slider__runway) {
  height: 6px;
}

.responsive-form.mobile :deep(.el-slider__button) {
  width: 24px;
  height: 24px;
  border: 3px solid var(--el-color-primary);
}

/* 日期选择器响应式样式 */
.responsive-form.mobile :deep(.el-date-editor) {
  width: 100%;
}

.responsive-form.mobile :deep(.el-date-editor .el-input__wrapper) {
  min-height: 44px;
}

/* 数字输入框响应式样式 */
.responsive-form.mobile :deep(.el-input-number) {
  width: 100%;
}

.responsive-form.mobile :deep(.el-input-number .el-input__wrapper) {
  min-height: 44px;
}

/* 表单操作按钮 */
.form-actions {
  display: flex;
  justify-content: flex-end;
  gap: 12px;
  margin-top: 32px;
  padding-top: 20px;
  border-top: 1px solid var(--el-border-color-lighter);
}

.form-actions.mobile-actions {
  flex-direction: column;
  gap: 12px;
  padding: 16px;
  background: var(--el-bg-color);
  border-top: 1px solid var(--el-border-color-lighter);
  position: sticky;
  bottom: 0;
  z-index: 10;
}

.form-actions.mobile-actions .el-button {
  width: 100%;
  min-height: 44px;
  font-size: 16px;
}

/* 抽屉表单样式 */
.drawer-form-content {
  height: 100%;
  display: flex;
  flex-direction: column;
}

.drawer-form-content :deep(.el-form) {
  flex: 1;
  padding: 0 20px;
  overflow-y: auto;
}

.drawer-actions {
  padding: 20px;
  border-top: 1px solid var(--el-border-color-lighter);
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.drawer-actions .el-button {
  min-height: 44px;
  font-size: 16px;
}

/* 内联表单样式 */
.responsive-form.inline :deep(.el-form-item) {
  display: inline-flex;
  margin-right: 16px;
  margin-bottom: 16px;
}

/* 错误状态样式 */
:deep(.el-form-item.is-error) {
  animation: shake 0.3s ease-in-out;
}

@keyframes shake {
  0%, 100% { transform: translateX(0); }
  25% { transform: translateX(-5px); }
  75% { transform: translateX(5px); }
}

/* 禁用状态样式 */
.responsive-form.disabled :deep(.el-form-item__label) {
  color: var(--el-text-color-disabled);
}

.responsive-form.disabled :deep(.el-input__wrapper) {
  background-color: var(--el-fill-color-light);
}

/* 焦点状态样式 */
:deep(.el-input__wrapper:focus-within),
:deep(.el-select .el-input__wrapper:focus-within),
:deep(.el-textarea__inner:focus) {
  box-shadow: 0 0 0 2px var(--el-color-primary-light-8);
}

/* 悬停状态样式 */
:deep(.el-input__wrapper:hover),
:deep(.el-select .el-input__wrapper:hover) {
  border-color: var(--el-color-primary);
}

/* 成功状态样式 */
:deep(.el-form-item.is-success) {
  margin-bottom: 20px;
}

/* 响应式网格布局 */
.form-grid {
  display: grid;
  gap: 20px;
}

.form-grid.cols-1 {
  grid-template-columns: 1fr;
}

.form-grid.cols-2 {
  grid-template-columns: repeat(2, 1fr);
}

.form-grid.cols-3 {
  grid-template-columns: repeat(3, 1fr);
}

.form-grid.cols-4 {
  grid-template-columns: repeat(4, 1fr);
}

/* 移动端网格调整 */
@media (max-width: 768px) {
  .form-grid.cols-2,
  .form-grid.cols-3,
  .form-grid.cols-4 {
    grid-template-columns: 1fr;
  }
}

@media (min-width: 769px) and (max-width: 1200px) {
  .form-grid.cols-3,
  .form-grid.cols-4 {
    grid-template-columns: repeat(2, 1fr);
  }
}

/* 响应式间距调整 */
@media (max-width: 480px) {
  :deep(.el-form-item) {
    margin-bottom: 20px;
  }

  .form-actions.mobile-actions {
    padding: 12px;
  }

  .drawer-form-content :deep(.el-form) {
    padding: 0 16px;
  }

  .drawer-actions {
    padding: 16px;
  }
}

/* 安全区域适配 */
@supports (padding: max(0px)) {
  .form-actions.mobile-actions {
    padding-bottom: max(16px, env(safe-area-inset-bottom));
  }

  .drawer-actions {
    padding-bottom: max(20px, env(safe-area-inset-bottom));
  }
}

/* 暗色主题优化 */
@media (prefers-color-scheme: dark) {
  .responsive-form.loading::after {
    background: rgba(0, 0, 0, 0.7);
  }
}

/* 打印样式 */
@media print {
  .form-actions {
    display: none;
  }

  .el-button {
    display: none;
  }

  .el-input__wrapper {
    border: 1px solid #000;
  }

  .el-form-item__label {
    color: #000;
  }
}
</style>